#include<bits/stdc++.h>
#define uint unsigned int
#define ll long long
#define ull unsigned long long
using namespace std;
namespace IO{
    char buff[1<<21],*p1=buff,*p2=buff;
    char getch(){
        return p1==p2&&(p2=((p1=buff)+fread(buff,1,1<<21,stdin)),p1==p2)?EOF:*p1++;
    }
    template<typename T>
    void read(T &x){
        char ch=getch();int fl=1;x=0;
        while(ch>'9'||ch<'0'){if(ch=='-')fl=-1;ch=getch();}
        while(ch<='9'&&ch>='0'){x=x*10+ch-48;ch=getch();}
        x*=fl;
    }
    template<typename T,typename ...Args>
    void read(T &x,Args& ...args){
        read(x);read(args...);
    }
    char obuf[1<<21],*p3=obuf;
    void putch(char ch){
        if(p3-obuf<(1<<21))*p3++=ch;
        else fwrite(obuf,p3-obuf,1,stdout),p3=obuf,*p3++=ch;
    }
    void pc(const char *s){
    	while(*s)putch(*s),s++;
    }
    char ch[100];
    template<typename T>
    void write(T x){
        if(!x)return putch('0');
        if(x<0)putch('-'),x*=-1;
        int top=0;
        while(x)ch[++top]=x%10+48,x/=10;
        while(top)putch(ch[top]),top--;
    }
    template<typename T,typename ...Args>
    void write(T x,Args ...args){
        write(x),putch(' '),write(args...);
    }
    void flush(){fwrite(obuf,p3-obuf,1,stdout);p3=obuf;}
}
using namespace IO;
inline int lowbit(int x){return x&(-x);}
const int N=3005;
int n,m;
ll ans;
char a[N][N];
int u[N][N],l[N][N],d[N][N],r[N][N];
vector<int>Del1[N],Del2[N];
struct BIT{
	int maxn;
	int tree[N];
	void Init(int x){
		maxn=x;
		fill(tree,tree+maxn+1,0);
	}
	inline void add(int x){
		while(x<=maxn){
			tree[x]++;
			x+=lowbit(x);
		}
	}
	inline int ask(int x){
		int sum=0;
		while(x){
			sum+=tree[x];
			x-=lowbit(x);
		}
		return sum;
	}
}T1,T2;
void sol(int l1,int r1,int l2,int r2){
	if(min(r1-l1,r2-l2)==0)return;
	if(r1-l1<=r2-l2){
		int mid=((l2+r2)>>1);
		for(int i=l1;i<=r1;i++){
			if(a[i][mid]!=a[i][mid+1])continue;
			int L=0,R=0;
			for(int j=i;j<=r1;j++)
				Del1[j].clear();
			for(int k=mid;k>=l2;k--){
				if(a[i][k]!=a[i][mid])break;
				Del1[d[i][k]].push_back(k);
				L=k;
			}
			for(int j=i;j<=r1;j++)
				Del2[j].clear();
			for(int k=mid+1;k<=r2;k++){
				if(a[i][k]!=a[i][mid+1])break;
				Del2[d[i][k]].push_back(k);
				R=k;
			}
			T1.Init(mid-l2+1);
			T2.Init(r2-mid);
			for(int j=i+1;j<=r1;j++){
				for(auto x:Del1[j-1]){
					T1.add(mid-x+1);
				}
				for(auto x:Del2[j-1]){
					T2.add(x-mid);
				}
				if(a[i][mid]!=a[j][mid])continue;
				if(a[i][mid+1]!=a[j][mid+1])continue;
				int cnt1=mid-max(L,l[j][mid])+1-T1.ask(mid-max(L,l[j][mid])+1);
				int cnt2=min(R,r[j][mid+1])-mid-T2.ask(min(R,r[j][mid+1])-mid);
				ans+=1ll*cnt1*cnt2;
			}
		}
		sol(l1,r1,l2,mid),sol(l1,r1,mid+1,r2);
	}else{
		int mid=((l1+r1)>>1);
		for(int i=l2;i<=r2;i++){
			if(a[mid][i]!=a[mid+1][i])continue;
			int L=0,R=0;
			for(int j=i;j<=r2;j++)
				Del1[j].clear();
			for(int k=mid;k>=l1;k--){
				if(a[k][i]!=a[mid][i])break;
				Del1[r[k][i]].push_back(k);
				L=k;
			}
			for(int j=i;j<=r2;j++)
				Del2[j].clear();
			for(int k=mid+1;k<=r1;k++){
				if(a[k][i]!=a[mid+1][i])break;
				Del2[r[k][i]].push_back(k);
				R=k;
			}
			T1.Init(mid-l1+1);
			T2.Init(r1-mid);
			for(int j=i+1;j<=r2;j++){
				for(auto x:Del1[j-1]){
					T1.add(mid-x+1);
				}
				for(auto x:Del2[j-1]){
					T2.add(x-mid);
				}
				if(a[mid][i]!=a[mid][j])continue;
				if(a[mid+1][i]!=a[mid+1][j])continue;
				int cnt1=mid-max(L,u[mid][j])+1-T1.ask(mid-max(L,u[mid][j])+1);
				int cnt2=min(R,d[mid+1][j])-mid-T2.ask(min(R,d[mid+1][j])-mid);
				ans+=1ll*cnt1*cnt2;
			}
		}
		sol(l1,mid,l2,r2),sol(mid+1,r1,l2,r2);
	}
}
signed main(){
	freopen("star.in","r",stdin);
	freopen("star.out","w",stdout);
	read(n,m);
	for(int i=1;i<=n;i++){
		for(int j=1;j<=m;j++){
			char ch=getch();
			while(ch<'a'||'z'<ch)ch=getch();
			a[i][j]=ch;
		}
	}
	for(int i=1;i<=n;i++){
		for(int j=1;j<=m;j++){
			if(i>1&&a[i-1][j]==a[i][j])u[i][j]=u[i-1][j];
			else u[i][j]=i;
			if(j>1&&a[i][j-1]==a[i][j])l[i][j]=l[i][j-1];
			else l[i][j]=j;
		}
	}
	for(int i=n;i>=1;i--){
		for(int j=m;j>=1;j--){
			if(i<n&&a[i+1][j]==a[i][j])d[i][j]=d[i+1][j];
			else d[i][j]=i;
			if(j<m&&a[i][j+1]==a[i][j])r[i][j]=r[i][j+1];
			else r[i][j]=j;
		}
	}
	sol(1,n,1,m);
	write(ans);
	return flush(),0;
}

